package ymos.steamcode.steamcode.controller;

import java.util.Base64;

import javax.crypto.Mac;
import javax.crypto.spec.SecretKeySpec;

public class SteamCodeGenerator {
	private static byte[] steamGuardCodeTranslations = "23456789BCDFGHJKMNPQRTVWXY".getBytes();

	public static String generateSteamGuardCodeForTime(long time,String shared_secret) throws Throwable {
		byte[] sharedSecretArray = FromBase64String(shared_secret);

		time /= 30;

		byte[] timeArray = new byte[8];

		for (int i = 8; i > 0; i--) {
			timeArray[i - 1] = (byte) (int) time;
			time >>>= 8;
		}
		byte[] hmac_result = encode(sharedSecretArray, timeArray);
		byte[] codeArray = new byte[5];
		try {
			int offset = hmac_result[19] & 15;
			int bin_code = (hmac_result[offset] & 127) << 24 | (hmac_result[offset + 1] & 255) << 16
					| (hmac_result[offset + 2] & 255) << 8 | hmac_result[offset + 3] & 255;
			for (int i = 0; i < 5; i++) {
				codeArray[i] = steamGuardCodeTranslations[bin_code % steamGuardCodeTranslations.length];
				bin_code /= steamGuardCodeTranslations.length;
			}

			return new String(codeArray);
		} catch (Exception ex) {
			return null;
		}
	}
	public static byte[] FromBase64String(String s) throws Throwable {
		try {
			return Base64.getDecoder().decode(s);
		} catch (Exception ex) {
			throw new Throwable("Invalid Base64 string!", ex);
		}
	}
	public static byte[] encode(byte[] key, byte[] value) {
		try {
			SecretKeySpec signingKey = new SecretKeySpec(key, "HmacSHA1");
			Mac mac = Mac.getInstance("HmacSHA1");
			
			mac.init(signingKey);
			
			return mac.doFinal(value);
		} catch (Exception e) {
			throw new RuntimeException(e);
		}
	}
}
